package iter3;

import java.awt.Color;
import java.awt.Cursor;
import java.awt.DisplayMode;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Point;
import java.awt.Toolkit;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;

import javax.swing.JFrame;
import javax.swing.JPanel;


public class BrickBreaker extends JFrame implements KeyListener
{
        
        private class BrickBreakerPanel extends JPanel implements MouseMotionListener, MouseListener
        {
                private Cegielka ceg [][];
                private Deska des;
                private Kulka kul;
                private Punkty pun;
                private Font czc;
                private boolean start;
                
                public BrickBreakerPanel(int xE, int yE)
                {
                        ceg = zbudujCegielki(xE, yE);
                        des = new Deska(xE, yE);
                        kul = new Kulka(xE, yE, des);
                        pun = new Punkty();
                        czc = new Font("Verdana", Font.BOLD, 10);
                        start = false;

                        addMouseMotionListener(this);
                        addMouseListener(this);
                        setFont(czc);
                }
                
                public Cegielka [][] getC()
                {
                        return ceg;
                }
                
                public Deska getD()
                {
                        return des;
                }
                
                public Kulka getK()
                {
                        return kul;
                }
                
                public Cegielka [][] zbudujCegielki(int xE, int yE)
                {
                        Cegielka [][] c = new Cegielka [10][20];
                        double ax = 0.005 * xE;
                        double ay = 0.04 * yE;
                        
                        for (int i = 0; i < 10; i++)
                        {
                                for (int j = 0; j < 20; j++)
                                {
                                        c[i][j] = new Cegielka();
                                        c[i][j].setX((int)(ax));
                                        c[i][j].setY((int)(ay));
                                        c[i][j].setW((int)(0.04 * xE));
                                        c[i][j].setH((int)(0.02 * yE));
                                        
                                        ax += 0.05 * xE;
                                }
                                
                                ay += 0.03 * yE;
                                ax = 0.005 * xE;
                        }
                        
                        return c;
                }
                
                public void wyswietlCegielki(Graphics g)
                {
                        for (int i = 0; i < ceg.length; i ++)
                                for (int j = 0; j < ceg[i].length; j++)
                                        ceg[i][j].wyswietlCegielke(g);
                }
                
                public void wyswietlDeske(Graphics g)
                {
                        des.wyswietlDeske(g);
                }
                
                public void wyswietlKulke(Graphics g)
                {
                        kul.wyswietlKulke(g);
                }
                
                public boolean czyZawiera(Kulka k, int x, int y)
                {
                        if (((x - k.getX() - k.getR() / 2) * (x - k.getX() - k.getR() / 2)) + ((y - k.getY() - k.getR() / 2) * (y - k.getY() - k.getR() / 2)) <= (k.getR() / 2) * (k.getR() / 2))
                                return true;
                        
                        return false;
                }
                
                public int yOdcinek(Odcinek o, int x)
                {
                        return ((o.getY2() - o.getY1()) * (x - o.getX1()) / (o.getX2() - o.getX1()) + o.getY1());
                }
                
                public boolean kolizjaKulkaOdcinek(Kulka k, Odcinek o)
                {
                        if (o.getX1() == o.getX2() && o.getY1() == o.getY2())
                                return czyZawiera(k, o.getX1(), o.getY1());
                        
                        else if (o.getX1() == o.getX2())
                        {
                                for (int i = o.getY1(); i <= o.getY2(); i++)
                                        if (czyZawiera(k, o.getX1(), i))
                                                return true;
                        }
                        
                        else if (o.getY1() == o.getY2())
                        {
                                for (int i = o.getX1(); i <= o.getX2(); i++)
                                        if (czyZawiera(k, i, o.getY1()))
                                                return true;
                        }
                        
                        else
                                for (int i = o.getX1(); i <= o.getX2(); i++)
                                        if (czyZawiera(k, i, yOdcinek(o, i)))
                                                return true;
                        
                        return false;
                }
                
                public int kolizjaKulkaCegielka(Kulka k, Cegielka c)
                {
                        if (c.getS() == false)
                                return -1;
                        
                        else
                                for (int i = 0; i < 4; i++)
                                        if (kolizjaKulkaOdcinek(k, c.zwrocOdcinek(i)))
                                                return i;
                        
                        return -1;
                }
                
                public int kolizjaKulkaBanda(Kulka k)
                {
                        if (k.getX() + k.getR() / 2 <= 0) 
                                return 3;
                        
                        else if ((k.getX() + k.getR() / 2) > Toolkit.getDefaultToolkit().getScreenSize().width)
                                return 1;
                        
                        else if ((k.getY() + k.getR() / 2) <= 0)
                                return 0;
                        
                        else if ((k.getY() + k.getR() / 2) > Toolkit.getDefaultToolkit().getScreenSize().height)
                                return 2;
                        
                        return -1;
                }
                
                public boolean kolizjaKulkaDeska(Kulka k, Deska d)
                {
                        return kolizjaKulkaOdcinek(k, d.zwrocOdcinek());
                }
                
                public boolean czyKoniec(Cegielka [][] c)
                {
                        for (int i = 0; i < c.length; i++)
                                for (int j = 0; j < c[i].length; j++)
                                        if (c[i][j].getS())
                                                return false;
                        
                        return true;
                }
                
                public void przesunKulke()
                {
                        kul.przesun();
                        
                        for (int i = 0; i < 10; i++)
                                for (int j = 0; j < 20; j++)
                                {
                                        int bok = -1;
                                        
                                        if ((bok = kolizjaKulkaCegielka(kul, ceg[i][j])) != -1)
                                        {
                                                ceg[i][j].setS(false);
                                                kul.zmienKatCegielkaBanda(bok);
                                                pun.dodajPunkty(10);
                                        }
                                }
                        
                        int bok = -1;
                        
                        if ((bok = kolizjaKulkaBanda(kul)) != -1)
                        {
                                kul.zmienKatCegielkaBanda(bok);
                                
                                if (bok == 2)
                                        pun.odejmijPunkty(10);
                                
                                for (int i = 0; i < 5; i++)
                                        kul.przesun();
                        }
                        
                        if (kolizjaKulkaDeska(kul, des))
                        {
                                kul.zmienKatDeska(des);
                                
                                for (int i = 0; i < 10; i++)
                                        kul.przesun();
                        }
                }
                
                public void wyswietlPunkty(Graphics g, Font f)
                {
                        String msgPoints = "Punkty: " + pun.toString();
                        FontMetrics fm = g.getFontMetrics();
                        
                        g.drawString(msgPoints, Toolkit.getDefaultToolkit().getScreenSize().width - fm.stringWidth(msgPoints) - 10, Toolkit.getDefaultToolkit().getScreenSize().height - 25);
                }
                
                
                
                public void paintComponent(Graphics g)
                {
                        super.paintComponent(g);
                        g.setColor(Color.blue);
                        wyswietlCegielki(g);
                        g.setColor(Color.green);
                        wyswietlDeske(g);
                        g.setColor(Color.red);
                        wyswietlKulke(g);
                
                        wyswietlPunkty(g, czc);
                        
                        if (start)
                                przesunKulke();
                        
                        if (pun.getQ() == 5 || czyKoniec(ceg))
                                start = false;
                }
                
                //@Override
                public void mouseDragged(MouseEvent me) {
                }

                //@Override
                public void mouseMoved(MouseEvent me) {
                        des.setX(me.getX() - des.getW() / 2);
                        
                        if (!start)
                                kul.setX(me.getX() - kul.getR() / 2);
                }

                //@Override
                public void mouseClicked(MouseEvent me) {
                        start = true;
                }

                //@Override
                public void mouseEntered(MouseEvent me) {
                }

                //@Override
                public void mouseExited(MouseEvent me) {
                }

                //@Override
                public void mousePressed(MouseEvent me) {
                }

                //@Override
                public void mouseReleased(MouseEvent me) {
                }
        }

        //@Override
        public void keyPressed(KeyEvent ke) {
                if (ke.getKeyCode() == KeyEvent.VK_ESCAPE)
                        System.exit(0);
        }

        //@Override
        public void keyReleased(KeyEvent ke) {
        }

        //@Override
        public void keyTyped(KeyEvent ke) {
        }

        public BrickBreaker()
        {
                BrickBreakerPanel p = new BrickBreakerPanel(Toolkit.getDefaultToolkit().getScreenSize().width, Toolkit.getDefaultToolkit().getScreenSize().height);
                add(p);
                
                addKeyListener(this);
                requestFocus();
                
                setUndecorated(true);
                setResizable(false);
                
                przelaczNaPelnyEkran();
                ukryjKursorMyszy();
                
                setVisible(true);
                setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                
                new Wat(p);
        }
        
        public void przelaczNaPelnyEkran()
        {
                DisplayMode displayMode = new DisplayMode(Toolkit.getDefaultToolkit().getScreenSize().width, Toolkit.getDefaultToolkit().getScreenSize().height, 24, 75);
                GraphicsEnvironment environment = GraphicsEnvironment.getLocalGraphicsEnvironment();
                GraphicsDevice device = environment.getDefaultScreenDevice();
                device.setFullScreenWindow(this);
                
                
                try 
                {
                        device.setDisplayMode(displayMode);
                } 
                catch (IllegalArgumentException e)
                {
                        System.out.println("Wyj¹tek!");
                }
        }
        
        public void ukryjKursorMyszy()
        {
                GraphicsEnvironment environment = GraphicsEnvironment.getLocalGraphicsEnvironment();
                GraphicsDevice device = environment.getDefaultScreenDevice();
                
                Cursor invisibleCursor = Toolkit.getDefaultToolkit().createCustomCursor(Toolkit.getDefaultToolkit().getImage(""), new Point(0, 0), "invisible");
                device.getFullScreenWindow().setCursor(invisibleCursor);
        }
        
}


